方法文档:将 JRuby 与 JMX 一起用于 Oracle WebLogic Server 11g

作者:Pas Apicella    

2011 年 4 月发布

JMX 技术(现在包括在 Java SE 平台中)为构建管理和监视设备、应用程序及服务驱动的网络的丰富模块化动态解决方案提供了工具。

本文介绍如何结合使用 JRuby 编程语言和 JMX 来查询 Oracle WebLogic Server 11g 第 1 版托管服务器以显示有关实例的运行时信息。

软件要求

假定安装了以下软件:

这些示例应该还可用于此软件的某些其他版本(但尚未在这些版本上进行测试)。

演示安装

  1. 验证是否已安装 JDK 1.6。
      
    $ java -version
    java version "1.6.0_23"
    Java(TM) SE Runtime Environment (build 1.6.0_23-b05)
    Java HotSpot(TM) 64-Bit Server VM (build 19.0-b09, mixed mode)
    
  2. 将 JRUBY_HOME 设置为 JRuby 的安装目录并验证 JRuby 是否运行。
    
    $ export JRUBY_HOME=$HOME/jruby-1.5.6
    $ export PATH=$PATH:$JRUBY_HOME/bin
    $ jruby -v
    jruby 1.5.6 (ruby 1.8.7 patchlevel 249) (2010-12-03 9cf97c3) 
     (Java HotSpot(TM) Client VM 1.6.0_22) [x86-java]
    
  3. 安装 jmx4r GEM 以便从 JRuby 获得 JMX 支持,如下所示。
    
    $ 
    jruby -S gem install jmx4r
    JRuby limited openssl loaded. http://jruby.org/openssl
    gem install jruby-openssl for full support.
    Successfully installed jmx4r-0.1.3
    1 gem installed
    Installing ri documentation for jmx4r-0.1.3...
    Installing RDoc documentation for jmx4r-0.1.3...
    
  4. 验证是否正确安装了 GEM jmx4r。
    
    $ jruby -S gem list
    *** LOCAL GEMS ***
    
    columnize (0.3.1)
    jmx4r (0.1.3)
    rake (0.8.7)
    rspec (1.3.0)
    ruby-debug (0.10.3)
    ruby-debug-base (0.10.3.2)
    sources (0.0.1)
    
  5. 确保有一个 weblogic 域,域中至少有一个托管服务器,并且可以从 Weblogic Server 控制台应用程序连接到该域,如下图所示。本例中使用的托管服务器名为 apple,运行在 7003 端口上,如下所示。
     

wls-jmx-jruby-f1

运行演示

  1. 第一个测试需要确保可以建立到 Weblogic 自身内部的 MBean 服务器的远程连接。代码文件名为 test_jmx_weblogic.rb,内容如下。MBean 服务器是所有 MBean 的信息库,为管理应用程序提供到 MBean 的访问。
    # verify JMX connection to WebLogic 11g Release 1
    require 'rubygems'
    require 'jmx4r'
    require '/u01/fmw/1034/wlserver_10.3/server/lib/wljmxclient.jar'
    
    java_import java.lang.System
    
    class VerifyWeblogicJMX
    
      def initialize(user, passwd, url)
        @user, @passwd, @url = user, passwd, url
    
        System.setProperty("jmx.remote.protocol.provider.pkgs", "weblogic.management.remote")
    
        @conn = JMX::MBean.establish_connection :url => url, :username => user, :password => passwd
      end
    
      # add getters and setters for all attrributes we wish to expose
      attr_reader :user, :passwd, :url, :conn
    
      def close
        @conn.close unless !@conn
      end
    
      def to_s
        "JMXConnection [user=#{@user}, passwd=#{@passwd}, " +
        "url=#{@url}]"
      end
    
    end
    
    username = "weblogic"
    password = "welcome1"
    url = "service:jmx:iiop://papicell-au.au.oracle.com:7003/jndi/weblogic.management.mbeanservers.runtime"
    
    print "Run at #{Time.now} using JRuby #{RUBY_VERSION}\n\n"
    
    begin
      test = VerifyWeblogicJMX.new(username, password, url)
      puts test
      puts "\nSuccessfully connected to Oracle Weblogic 10.3.x from JRuby using JMX "
    rescue
      puts "\n** Error occured **\n"
      puts "Failed executing Oracle Weblogix JMX demo from JRuby ", $!, "\n"
    ensure
      test.close
    end
    
    print "Ended at #{Time.now}"
    
  2. 编辑以下代码以连接到 WebLogic 服务器。URL 的格式如下所示。


    service:jmx:iiop://{主机名}:{托管服务器端口}/jndi/weblogic.management.mbeanservers.runtime

    编辑以下代码以确保使用 Weblogic JMX 客户端 JAR 文件。此文件位于 $WLS_HOME/server/lib 目录中。
    require '/u01/fmw/1034/wlserver_10.3/server/lib/wljmxclient.jar'
    请确保指定正确的服务器连接凭证。
    
    username = "weblogic"
    password = "welcome1"
    url = "service:jmx:iiop://papicell-au.au.oracle.com:7003/jndi/weblogic.management.mbeanservers.runtime"
    
  3. 使用 JRuby 运行 test_jmx_connection.rb,如下所示。
    
    $ jruby test_jmx_weblogic.rb
    Run at Thu Mar 31 08:09:49 +1100 2011 using JRuby 1.8.7
    
    JMXConnection [user=weblogic, passwd=welcome1,
      url=service:jmx:iiop://papicell-au.au.oracle.com:7003/jndi/weblogic.management.mbeanservers.runtime]
    
    Successfully connected to Oracle Weblogic 10.3.x from JRuby using JMX
    
    Ended at Thu Mar 31 08:09:50 +1100 2011
    
  4. 现在可以开始连接;我们将只查询一个 MBean,并获取有关正在运行的 JVM 的运行时统计信息。程序将执行以下操作:
    • 使用 JMX 连接到 Weblogic 托管服务器
    • 使用如下所示的名称查找/查询 MBean — com.bea:ServerRuntime=apple,Name=apple,Type=JVMRuntime
    • 进入循环,在每次请求之间暂停 30 秒以等待 MBean 数据
    代码文件名为 monitor-mbean.rb,文件中包含以下内容:
    
    require 'rubygems'
    require 'jmx4r'
    require '/u01/fmw/1034/wlserver_10.3/server/lib/wljmxclient.jar'
    
    java_import 'javax.management.ObjectName'
    java_import java.lang.System
    
    def display_array (value)
      data = ""
      value.each do |x|
        data += "\n\t" + x.to_s
      end
      return data
    end
    
    # method used to check if the attribute data contains an array of data and make some sort of effort
    # to display it as text. This is quick and dirty way to do this but generally works for most array 
    # attribute values. If not an array it simply display the attribute value as a string
    
    def display_attribute_data(conn, object_name, attribute)   
      s = conn.get_attribute object_name, attribute
      search_str = s.to_s
     
      if (/^\[Ljava.lang.String/.match(search_str)) or
         (/^\[I/.match(search_str)) or
         (/^\[Ljavax.management.ObjectName/.match(search_str))
        # we have a array with data
        return display_array s
      end
     
      return s;
    end
    
    class JMXConnection
    
      def initialize(user, passwd, url)
        @user, @passwd, @url = user, passwd, url
    
        System.setProperty("jmx.remote.protocol.provider.pkgs", "weblogic.management.remote")
    
        @conn = JMX::MBean.establish_connection :url => url, :username => user, :password => passwd
      end
    
      # add getters and setters for all attrributes we wish to expose
      attr_reader :user, :passwd, :url, :conn
    
      def close
        @conn.close unless !@conn
      end
    
      def to_s
        "JMXConnection [user=#{@user}, passwd=#{@passwd}, " +
        "url=#{@url}]"
      end
    
    end
    
    username = "weblogic"
    password = "welcome1"
    url = "service:jmx:iiop://papicell-au.au.oracle.com:7003/jndi/weblogic.management.mbeanservers.runtime"
    
    print "Run at #{Time.now} using JRuby #{RUBY_VERSION}\n\n"
    
    begin
      jmx_conn = JMXConnection.new(username, password, url)
      puts jmx_conn
      puts "\nSuccessfully connected to Oracle Weblogic 10.3.x from JRuby using JMX "
     
      wls_mbean_name = "com.bea:ServerRuntime=apple,Name=apple,Type=JVMRuntime"
    
      mbean = JMX::MBean.find_by_name wls_mbean_name
      java_object_name = ObjectName.new wls_mbean_name
    
    
      while (true)
        # display attributes key/values
        mbean.attributes.each do |key, value|
          puts "Name: #{value}, Value: #{display_attribute_data jmx_conn.conn, java_object_name, value}\n"
        end
    
        # sleep for 30 seconds
        puts "\nSleeping for 30 seconds....\n"
        sleep 30
      end
    
    
    rescue
      puts "\n** Error occured **\n"
      puts "Failed executing Oracle Weblogix JMX demo from JRuby ", $!, "\n"
    ensure
      jmx_conn.close
    end
    
    print "Ended at #{Time.now}\n"
    
  5. 编辑以下代码以确保使用 Weblogic JMX 客户端 JAR 文件。该文件位于 $WLS_HOME/server/lib 目录中。
    
    require '/u01/fmw/1034/wlserver_10.3/server/lib/wljmxclient.jar'
    
    请确保指定正确的服务器连接凭证。
    
    username = "weblogic"
    password = "welcome1"
    url = "service:jmx:iiop://papicell-au.au.oracle.com:7003/jndi/weblogic.management.mbeanservers.runtime"
     
  6. 验证输出,如下所示。您将注意到,每次迭代后,“HeapFreePercent”和“HeapFreeCurrent”等属性的值将随着托管服务器 JVM 上的负载而变化。(注:为便于阅读,已省略“ThreadStackDump”的大多数线程转储属性数据。)
    $ jruby monitor-mbean.rb
    
    Run at Mon Apr 04 10:26:46 +1000 2011 using JRuby 1.8.7
    
    JMXConnection [user=weblogic, passwd=welcome1,
       url=service:jmx:iiop://papicell-au.au.oracle.com:7003/jndi/weblogic.management.mbeanservers.runtime]
    Successfully connected to Oracle Weblogic 10.3.x from JRuby using JMX
    Name: Parent, Value: com.bea:Name=apple,Type=ServerRuntime
    Name: Uptime, Value: 2772452
    Name: HeapFreePercent, Value: 90
    Name: JavaVersion, Value: 1.6.0_22
    Name: Type, Value: JVMRuntime
    Name: ThreadStackDump, Value: "[STANDBY] ExecuteThread: '3' for queue: 
      'weblogic.kernel.Default (self-tuning)'" waiting for lock weblogic.work.ExecuteThread@1f2caf4 WAITING
     java.lang.Object.wait(Native Method)
     java.lang.Object.wait(Object.java:485)
     weblogic.work.ExecuteThread.waitForRequest(ExecuteThread.java:160)
     weblogic.work.ExecuteThread.run(ExecuteThread.java:181)
    
    "DynamicListenThread[Default[1]]" RUNNABLE native
     java.net.PlainSocketImpl.socketAccept(Native Method)
     java.net.PlainSocketImpl.accept(PlainSocketImpl.java:390)
     
    .....
    
    Name: OSVersion, Value: 5.10
    Name: JavaVendor, Value: Sun Microsystems Inc.
    Name: HeapFreeCurrent, Value: 210922280
    Name: OSName, Value: SunOS
    Name: Name, Value: apple
    Name: HeapSizeMax, Value: 518979584
    Name: JavaVMVendor, Value: Sun Microsystems Inc.
    Name: HeapSizeCurrent, Value: 259522560
    
    Sleeping for 30 seconds....
    
    Name: Parent, Value: com.bea:Name=apple,Type=ServerRuntime
    Name: Uptime, Value: 2802565
    Name: HeapFreePercent, Value: 90
    Name: JavaVersion, Value: 1.6.0_22
    Name: Type, Value: JVMRuntime
    Name: ThreadStackDump, Value: "[STANDBY] ExecuteThread: '3' for queue: 
      'weblogic.kernel.Default (self-tuning)'" waiting for lock weblogic.work.ExecuteThread@1f2caf4 WAITING
     java.lang.Object.wait(Native Method)
    
    .......
    
    Name: OSVersion, Value: 5.10
    Name: JavaVendor, Value: Sun Microsystems Inc.
    Name: HeapFreeCurrent, Value: 210225232
    Name: OSName, Value: SunOS
    Name: Name, Value: apple
    Name: HeapSizeMax, Value: 518979584
    Name: JavaVMVendor, Value: Sun Microsystems Inc.
    Name: HeapSizeCurrent, Value: 259522560
    
    Sleeping for 30 seconds....
  7. 使用 CTRL-C 结束程序。

祝贺您,您已经了解了如何结合使用 JMX 和 JRuby 访问 Weblogic Server。您可以使用这种设置动态检查属性值,并在这些值高于或低于预期值时向管理员发送警报。